package com.application.easemob;

import com.application.easemob.api.EasemobChatGroups;
import com.application.easemob.api.EasemobIMUsers;
import com.application.easemob.comm.Constants;
import com.fasterxml.jackson.databind.node.ArrayNode;
import com.fasterxml.jackson.databind.node.JsonNodeFactory;
import com.fasterxml.jackson.databind.node.ObjectNode;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;

import java.util.ArrayList;
import java.util.List;
import java.util.regex.Matcher;
import java.util.regex.Pattern;

/**
 * Created by PC on 2015/8/4.
 */
public class EasemobHelper {

    private static final Logger LOGGER = LoggerFactory.getLogger(EasemobHelper.class);

    private final static int TRY_COUNT = 3;

    public static void main(String[] args) {
//        EasemobHelper.createUser(324L);
        createGroup("神马队", new String[]{"1"});
//        deleteUser(324L);
//        updateGroup("90939382839640520","好好看");
//        createUser(1L);
    }

    public static void createUser(String userId) {
        createUser(userId, TRY_COUNT);
    }

    public static void createUsers(String[] userIds) {
        createUsers(userIds, TRY_COUNT);
    }

    /**
     * 注册IM用户[单个]
     */
    public static void createUser(String userId, int n) {
        try {
            ObjectNode datanode = JsonNodeFactory.instance.objectNode();
            datanode.put("username", userId);
            datanode.put("password", Constants.DEFAULT_PASSWORD);
            ObjectNode node = EasemobIMUsers.createNewIMUserSingle(datanode);
            handlerResult(node);
        } catch (Exception e) {
            if (n > 0) {
                createUser(userId, --n);
            } else {
                throw new RuntimeException("创建用户失败：" + e.getMessage());
            }
        }

    }

    /**
     * 注册IM用户[批量]
     */
    public static void createUsers(String[] userIds, int n) {
        try {
            ArrayNode jsonNodes = JsonNodeFactory.instance.arrayNode();
            for (int i = 0; i < userIds.length; i++) {
                ObjectNode datanode = JsonNodeFactory.instance.objectNode();
                datanode.put("username", userIds[i]);
                datanode.put("password", Constants.DEFAULT_PASSWORD);
                jsonNodes.add(datanode);
            }
            ObjectNode node = EasemobIMUsers.createNewIMUserBatch(jsonNodes);
            handlerResult(node);
        } catch (Exception e) {
            System.out.println(e);
            if (n > 0) {
                createUsers(userIds, --n);
            } else {
                throw new RuntimeException("批量创建用户失败：" + e.getMessage());
            }
        }

    }

    private static void handlerResult(ObjectNode node) {
        System.out.println(node);
        if (null == node) {
            throw new RuntimeException(node.findValue("error_description").toString());
        } else if (!node.findValue("statusCode").toString().equals("200")) {
            String val = node.findValue("error").toString();
            if ("\"duplicate_unique_property_exists\"".equals(val)) {
                return;
            } else if ("\"illegal_argument\"".equals(val)) {
                throw new IllegalArgumentException(node.findValue("error_description").toString());
            } else if (node.findValue("error_description").toString().contains("doesn't exist!")) {//用户不存在
                return;
            }
            throw new RuntimeException(node.findValue("error_description").toString());
        }
    }

    /**
     * 删除IM用户[单个]
     */
    public static void deleteUser(String userId) {
        deleteUser(userId, TRY_COUNT);
    }

    public static void deleteUser(String userId, int n) {
        try {
            ObjectNode node = EasemobIMUsers.deleteIMUserByuserName(userId.toString());
            if (null != node) {
                LOGGER.info("删除用户：" + node.toString());
            }
            handlerResult(node);
        } catch (Exception e) {
            if (n > 0) {
                deleteUser(userId, --n);
            } else {
                throw new RuntimeException("删除用户失败：" + e.getMessage());
            }
        }
    }

    /**
     * 创建群组,同时加入群成员并返回群组ID(若不存在群成员则先进行添加)
     *
     * @param groupName
     * @param userIds
     */
    public static String createGroupAtAll(String groupName, String[] userIds) {
        //如果创建返回illegal_argument错误
        String groupId = createGroup(groupName, userIds);
        if (groupId == null || "".equals(groupId)) {
            for (String userId : userIds) {
                createUser(userId);
            }
            groupId = EasemobHelper.createGroup(groupName, userIds);
        }
        return groupId;
    }

    /**
     * 创建群组,同时加入群成员并返回群组ID
     *
     * @param groupName
     * @param userIds
     */
    public static String createGroup(String groupName, String[] userIds) {
        for (String userId : userIds) {
            ObjectNode node = EasemobIMUsers.getIMUsersByUserName(userId.toString());
            if (!node.findValue("statusCode").toString().equals("200")) {//群用户不存在则创建
                EasemobHelper.createUser(userId);
            }
        }
        return createGroup(groupName, userIds, TRY_COUNT);
    }

    public static String createGroup(String groupName, String[] userIds, int n) {
        try {
            ObjectNode dataObjectNode = JsonNodeFactory.instance.objectNode();
            dataObjectNode.put("groupname", groupName);
            dataObjectNode.put("desc", groupName);
            dataObjectNode.put("approval", true);
            dataObjectNode.put("public", true);
            dataObjectNode.put("maxusers", 333);
            dataObjectNode.put("owner", userIds[0].toString());
            ArrayNode arrayNode = JsonNodeFactory.instance.arrayNode();
            for (String userId : userIds) {
                if (!userId.equals(userIds[0])) {
                    arrayNode.add(userId.toString());
                }
            }
            dataObjectNode.put("members", arrayNode);
            ObjectNode node = EasemobChatGroups.creatChatGroups(dataObjectNode);

            handlerResult(node);
            return node.findValue("data").findValue("groupid").toString().replaceAll("\"", "");
        } catch (IllegalArgumentException e) {
            return "";
        } catch (Exception e) {
            if (n > 0) {
                createGroup(groupName, userIds, --n);
            } else {
                e.printStackTrace();
                throw new RuntimeException("创建群组失败：" + e.getMessage());
            }
        }
        return null;
    }

    /**
     * 删除群组
     *
     * @param groupId
     */
    public static void deleteGroup(String groupId) {
        deleteGroup(groupId, TRY_COUNT);
    }

    public static void deleteGroup(String groupId, int n) {
        if (groupId == null) {
            return;
        }
        try {
            ObjectNode deleteChatGroupNode = EasemobChatGroups.deleteChatGroups(groupId);
            handlerResult(deleteChatGroupNode);
        } catch (Exception e) {
            if (n > 0) {
                deleteGroup(groupId, --n);
            } else {
                throw new RuntimeException("删除群组失败：" + e.getMessage());
            }
        }
    }

    /**
     * 修改群组名称
     *
     * @param groupId
     * @param groupName
     */
    public static void updateGroup(String groupId, String groupName) {
        updateGroup(groupId, groupName, TRY_COUNT);
    }

    /**
     * 修改群组群主
     *
     * @param groupId
     * @param teacherId
     */
    public static void updateGroupOwner(String groupId, String teacherId) {
        updateGroupOwner(groupId, teacherId, TRY_COUNT);
    }

    public static void updateGroupOwner(String groupId, String teacherId, int n) {
        if (groupId == null) {
            return;
        }
        try {
            ObjectNode dataNode = JsonNodeFactory.instance.objectNode();
            dataNode.put("newowner", teacherId.toString());
            ObjectNode deleteChatGroupNode = EasemobChatGroups.updateChatGroups(groupId, dataNode);
            handlerResult(deleteChatGroupNode);
        } catch (Exception e) {
            if (n > 0) {
                updateGroupOwner(groupId, teacherId, --n);
            } else {
                throw new RuntimeException("更改群组失败：" + e.getMessage());
            }
        }
    }

    public static void updateGroup(String groupId, String groupName, int n) {
        if (groupId == null) {
            return;
        }
        try {
            ObjectNode dataNode = JsonNodeFactory.instance.objectNode();
            dataNode.put("groupname", groupName);
            ObjectNode deleteChatGroupNode = EasemobChatGroups.updateChatGroups(groupId, dataNode);
            handlerResult(deleteChatGroupNode);
        } catch (Exception e) {
            if (n > 0) {
                updateGroup(groupId, groupName, --n);
            } else {
                throw new RuntimeException("更改群组名称失败：" + e.getMessage());
            }
        }
    }

    /**
     * 群组添加用户
     *
     * @param groupId
     * @param userId
     */
    public static void addUserToGroup(String groupId, String userId) {
        addUserToGroup(groupId, userId, TRY_COUNT);
    }


    public static void addUserToGroup(String groupId, String userId, int n) {
        if (groupId == null) {
            return;
        }
        try {
            ObjectNode addUserToGroupNode = EasemobChatGroups.addUserToGroup(groupId, userId.toString());
            handlerResult(addUserToGroupNode);
        } catch (Exception e) {
            if (n > 0) {
                createUser(userId, 1);
                addUserToGroup(groupId, userId, --n);
            } else {
                throw new RuntimeException("用户加入群组失败：" + e.getMessage());
            }
        }

    }

    /**
     * 群组删除用户
     *
     * @param groupId
     * @param userId
     */
    public static void deleteUserFromGroup(String groupId, String userId) {
        if (groupId != null) {
            ObjectNode deleteUserFromGroupNode = EasemobChatGroups.deleteUserFromGroup(groupId, userId.toString());
            handlerResult(deleteUserFromGroupNode);
        }
    }

    public static void deleteUserFromGroup(String groupId, String userId, int n) {
        if (groupId != null) {
            try {
                ObjectNode deleteUserFromGroupNode = EasemobChatGroups.deleteUserFromGroup(groupId, userId.toString());
                handlerResult(deleteUserFromGroupNode);
            } catch (Exception e) {
                if (n > 0) {
                    deleteGroup(groupId, --n);
                } else {
                    throw new RuntimeException("用户移除群组失败：" + e.getMessage());
                }
            }
        }
    }

    public static void activate(String userId, int n) {
        try {
            ObjectNode node = EasemobIMUsers.activate(userId.toString());
            handlerResult(node);
        } catch (Exception e) {
            if (n > 0) {
                activate(userId, --n);
            } else {
                throw new RuntimeException("激活用户失败" + e.getMessage());
            }
        }

    }

    public static void deactivate(String userId, int n) {
        try {
            ObjectNode node = EasemobIMUsers.deactivate(userId.toString());
            handlerResult(node);
        } catch (Exception e) {
            if (n > 0) {
                deactivate(userId, --n);
            } else {
                throw new RuntimeException("禁用用户失败" + e.getMessage());
            }
        }

    }

    public static List<String> getGroupUserList(String groupId, int n) {
        List<String> list = new ArrayList<>();

        try {
            ObjectNode getAllMemberssByGroupIdNode = EasemobChatGroups.getAllMemberssByGroupId(groupId);
            handlerResult(getAllMemberssByGroupIdNode);

            String str = getAllMemberssByGroupIdNode.findValue("data").toString();

            Matcher matcher = Pattern.compile("\"([\\d]+)\"").matcher(str);
            while (matcher.find()) {
                list.add(String.valueOf(matcher.group(1)));
            }
        } catch (Exception e) {
            if (n > 0) {
                getGroupUserList(groupId, --n);
            } else {
                throw new RuntimeException(e.getMessage());
            }
        }
        return list;
    }
}
